package drds.global_transaction;


import drds.common.$;
import drds.common.Author;
import lombok.extern.slf4j.Slf4j;

import java.io.UnsupportedEncodingException;
import java.net.NetworkInterface;
import java.util.Enumeration;
import java.util.Random;
import java.util.concurrent.atomic.AtomicInteger;

@Author(name = Authors.LI_YANG)
@Slf4j
public class TransactionIdFactory
{
    public static final int GLOBAL_TRANSACTION_LENGTH = 20;
    static final int SIZE_OF_MAC = 6;
    static final Random random = new Random();
    static final AtomicInteger index = new AtomicInteger();
    static String hardwareAddress = "drds";

    static
    {
        hardwareAddress = getHardwareAddress();
    }

    private static String getHardwareAddress()
    {
        Enumeration<NetworkInterface> enumeration = null;
        try
        {
            enumeration = NetworkInterface.getNetworkInterfaces();
        } catch (Exception e)
        {
            log.error("读取mac失败", $.printStackTraceToString(e));
            throw new RuntimeException("读取mac失败", e);
        }
        String mac = null;
        while (mac == null && enumeration != null && enumeration.hasMoreElements())
        {
            NetworkInterface networkInterface = enumeration.nextElement();
            try
            {
                if (networkInterface.isUp() == false)
                {
                    continue;
                } else if (networkInterface.isPointToPoint() || networkInterface.isVirtual())
                {
                    continue;
                } else if (networkInterface.isLoopback())
                {
                    continue;
                }
                byte[] hardwareAddress = networkInterface.getHardwareAddress();
                if (hardwareAddress == null || hardwareAddress.length != SIZE_OF_MAC)
                {
                    continue;
                }
                mac = new String(hardwareAddress);
                return Md5.md5(mac);
            } catch (Exception rex)
            {
                log.debug(rex.getMessage(), rex);
            }
        }
        throw new IllegalStateException("not find mac");
    }


    public static final String createTransactionId() throws UnsupportedEncodingException
    {
        StringBuilder sb = new StringBuilder(hardwareAddress);
        long currentTimeMillis = System.currentTimeMillis();
        sb.append(currentTimeMillis);
        short value = (short) (index.incrementAndGet() % Short.MAX_VALUE);
        sb.append(value);
        sb.append(random.nextInt(10000));
        return sb.toString();
    }

    public final static String globalTransactionIdWithBranchTransactionId(String globalTransactionId, String branchTransactionId)
    {
        return globalTransactionId + "_" + branchTransactionId;
    }
}
